return result;
}
+static void vmx_vioapic_update_imr(struct vmx_vioapic *s, int index)
+{
+ if (s->redirtbl[index].RedirForm.mask)
+ set_bit(index, &s->imr);
+ else
+ clear_bit(index, &s->imr);
+}
+
static void vmx_vioapic_write_indirect(struct vmx_vioapic *s,
unsigned long addr,
unsigned long length,
redir_content = ((redir_content >> 32) << 32) |
(val & 0xffffffff);
s->redirtbl[redir_index].value = redir_content;
+ vmx_vioapic_update_imr(s, redir_index);
} else {
printk("vmx_vioapic_write_indirect "
"error register %x\n", s->ioregsel);
memset(s, 0, sizeof(vmx_vioapic_t));
- for (i = 0; i < IOAPIC_NUM_PINS; i++)
+ for (i = 0; i < IOAPIC_NUM_PINS; i++) {
s->redirtbl[i].RedirForm.mask = 0x1;
+ vmx_vioapic_update_imr(s, i);
+ }
}
static void ioapic_update_config(vmx_vioapic_t *s,
target = apic_round_robin(
s->domain, dest_mode, vector, deliver_bitmask);
- ioapic_inj_irq(s, target, vector, trig_mode, delivery_mode);
+ if (target)
+ ioapic_inj_irq(s, target, vector, trig_mode, delivery_mode);
+ else{
+ VMX_DBG_LOG(DBG_LEVEL_IOAPIC, "ioapic deliver "
+ "null round robin mask %x vector %x delivery_mode %x\n",
+ deliver_bitmask, vector, deliver_bitmask);
+ }
break;
}
ASSERT(s);
- irqs = s->irr & ~s->isr;
+ irqs = s->irr & ~s->isr & ~s->imr;
return __fls(irqs);
}
VMX_DBG_LOG(DBG_LEVEL_IOAPIC, "service_ioapic "
"highest irqno %x\n", irqno);
- if (!s->redirtbl[irqno].RedirForm.mask) {
+ if (!test_bit(irqno, &s->imr)) {
ioapic_deliver(s, irqno);
}
if (!vmx_apic_support(d))
return;
- s->irr |= irqs;
+ s->irr |= irqs & ~s->imr;
service_ioapic(s);
}
domain_crash_synchronous();
}
- s->lapic_info[s->lapic_count ++] = vlapic;
+ /* update count later for race condition on interrupt */
+ s->lapic_info[s->lapic_count] = vlapic;
+ s->lapic_count ++;
return s->lapic_count;
}